package com.example.newdemo.http;

import android.os.Environment;
import android.os.Handler;
import android.os.Message;
import android.widget.TextView;

import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;

public class HttpURLConnectionsUtils {


    private TextView mTvMsg;

    private String result = null;


    public void httpClientDemo(){


    }


    /**
     * fileName 文件名(不带后缀)
     * filePath 文件的本地路径 (xxx / xx / test.jpg)
     */
    public void uploadFile(String fileName , String filePath) {

        HttpURLConnection conn = null;

        /// boundary就是request头和上传文件内容的分隔符(可自定义任意一组字符串)
        String BOUNDARY = "******";
        // 用来标识payLoad+文件流的起始位置和终止位置(相当于一个协议,告诉你从哪开始,从哪结束)
        String  preFix = ("\r\n--" + BOUNDARY + "--\r\n");

        try {
            // (HttpConst.uploadImage 上传到服务器的地址
            URL url = new URL("www.baidu.com");
            conn = (HttpURLConnection) url.openConnection();
            conn.setConnectTimeout(5000);
            conn.setReadTimeout(30000);
            conn.setDoOutput(true);
            conn.setDoInput(true);
            conn.setUseCaches(false);
            // 设置请求方法
            conn.setRequestMethod("POST");
            // 设置header
            conn.setRequestProperty("Accept","*/*");
            conn.setRequestProperty("Connection", "keep-alive");
            conn.setRequestProperty("Content-Type", "multipart/form-data; boundary=" + BOUNDARY);

            // 获取写输入流
            OutputStream out = new DataOutputStream(conn.getOutputStream());

            // 获取上传文件
            File file = new File(filePath);

            // 要上传的数据
            StringBuffer strBuf = new StringBuffer();

            // 标识payLoad + 文件流的起始位置
            strBuf.append(preFix);

            // 下面这三行代码,用来标识服务器表单接收文件的name和filename的格式
            // 在这里,我们是file和filename.后缀[后缀是必须的]。
            // 这里的fileName必须加个.jpg,因为后台会判断这个东西。
            // 这里的Content-Type的类型,必须与fileName的后缀一致。
            // 如果不太明白,可以问一下后台同事,反正这里的name和fileName得与后台协定！
            // 这里只要把.jpg改成.txt，把Content-Type改成上传文本的类型，就能上传txt文件了。
            strBuf.append("Content-Disposition: form-data; name=\"file\"; filename=\"" + fileName+".jpg" + "\"\r\n");
            strBuf.append("Content-Type: image/jpeg"  + "\r\n\r\n");
            out.write(strBuf.toString().getBytes());

            // 获取文件流
            FileInputStream fileInputStream = new FileInputStream(file);
            DataInputStream inputStream = new DataInputStream(fileInputStream);

            // 每次上传文件的大小(文件会被拆成几份上传)
            int bytes = 0;
            // 计算上传进度
            float count = 0;
            // 获取文件总大小
            int fileSize = fileInputStream.available();
            // 每次上传的大小
            byte[] bufferOut = new byte[1024];
            // 上传文件
            while ((bytes = inputStream.read(bufferOut)) != -1) {
                // 上传文件(一份)
                out.write(bufferOut, 0, bytes);
                // 计算当前已上传的大小
                count += bytes;
                // 打印上传文件进度(已上传除以总大*100就是进度)
//                utils.logD("progress:" +(count / fileSize * 100) +"%");
            }

            // 关闭文件流
            inputStream.close();

            // 标识payLoad + 文件流的结尾位置
            out.write(preFix.getBytes());

            // 至此上传代码完毕

            // 总结上传数据的流程：preFix + payLoad(标识服务器表单接收文件的格式) + 文件(以流的形式) + preFix
            // 文本与图片的不同,仅仅只在payLoad那一处的后缀的不同而已。

            // 输出所有数据到服务器
            out.flush();

            // 关闭网络输出流
            out.close();

            // 重新构造一个StringBuffer,用来存放从服务器获取到的数据
            strBuf = new StringBuffer();

            // 打开输入流 , 读取服务器返回的数据
            BufferedReader reader = new BufferedReader(new InputStreamReader(conn.getInputStream()));

            String line;

            // 一行一行的读取服务器返回的数据
            while ((line = reader.readLine()) != null) {
                strBuf.append(line).append("\n");
            }

            // 关闭输入流
            reader.close();

            // 打印服务器返回的数据
//            utils.logD("上传成功:"+strBuf.toString());

        } catch (Exception e) {
//            utils.logD("上传图片出错:"+e.toString());
        } finally {
            if (conn != null) {
                conn.disconnect();
            }
        }

    }



    public void httpRequest(){

        try {
            // 1. 得到访问地址的URL
            URL url = new URL("http://localhost:8080/Servlet/do_login.do?username=test&password=123456");

            // 2. 得到网络访问对象java.net.HttpURLConnection
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();

            /* 3. 设置请求参数（过期时间，输入、输出流、访问方式），以流的形式进行连接 */
            connection.setDoOutput(false);                  // 设置是否向HttpURLConnection输出

            connection.setDoInput(true);                    // 设置是否从httpUrlConnection读入

            connection.setRequestMethod("GET");              // 设置请求方式

            connection.setUseCaches(true);                  // 设置是否使用缓存

            connection.setInstanceFollowRedirects(true);     // 设置此 HttpURLConnection 实例是否应该自动执行 HTTP 重定向

            connection.setConnectTimeout(3000);             // 设置超时时间

            connection.connect();                           // 连接       url.openConnection()至此的配置必须要在connect之前完成，

            // 4. 得到响应状态码的返回值 responseCode
            int code = connection.getResponseCode();

            // 5. 如果返回值正常，数据在网络中是以流的形式得到服务端返回的数据
            String msg = "";

            if (code == 200) {          // 正常响应
                                        // 从流中读取响应信息
                BufferedReader reader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
                String line = null;

                while ((line = reader.readLine()) != null) { // 循环从流中读取
                    msg += line + "\n";
                }
                reader.close(); // 关闭流
            }

            // 6. 断开连接，释放资源
            connection.disconnect();


            System.out.println(msg);                           // 显示响应结果
        } catch (IOException e) {
            e.printStackTrace();
        }



    }




    private Thread fileThread = new Thread(){
        public void run() {
            HttpURLConnection connection = null;
            try {
                URL url = new URL("http://192.168.23.1:8080/TestProject/FileTest");
                connection = (HttpURLConnection) url.openConnection();
                // 设置每次传输的流大小，可以有效防止手机因为内存不足崩溃
                // 此方法用于在预先不知道内容长度时启用没有进行内部缓冲的 HTTP请求正文的流。
                connection.setChunkedStreamingMode(51200); // 128K
                // 不使用缓存
                connection.setUseCaches(false);
                // 设置请求方式
                connection.setRequestMethod("POST");
                // 设置编码格式
                connection.setRequestProperty("Charset", "UTF-8");
                // 设置容许输出
                connection.setDoOutput(true);

                // 上传文件
                FileInputStream file = new FileInputStream(Environment.getExternalStorageDirectory().getPath() + "/aaaaa/baidu_map.apk");


                OutputStream os = connection.getOutputStream();
                byte[] b = new byte[1024];
                int count = 0;
                while((count = file.read(b)) != -1){
                    os.write(b, 0, count);
                }
                os.flush();
                os.close();

                // 获取返回数据
                if(connection.getResponseCode() == 200){
                    InputStream is = connection.getInputStream();
                    result = inputStreamToString(is,"UTF-8");

                    Message msg = Message.obtain();
                    msg.what = 0;
                    fileHandler.sendMessage(msg);
                }
            } catch (MalformedURLException e) {
                e.printStackTrace();
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                if(connection != null){
                    connection.disconnect();
                }
            }
        };
    };



    public static String inputStreamToString(InputStream inputStream,String chartSet){
        StringBuilder builder=new StringBuilder();
        try {
            BufferedReader br=new BufferedReader(new InputStreamReader(inputStream,chartSet));
            String con;
            while ((con=br.readLine())!=null){
                builder.append(con);
            }
            br.close();
            return builder.toString();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";
    }

    private Handler fileHandler = new Handler(){
        public void handleMessage(android.os.Message msg) {
            if(msg.what == 0 && result!=null){
                mTvMsg.setText(result);
            }
        };
    };










}
